package com.xmy.cultivate.service.impl;

import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.xmy.cultivate.entity.*;
import com.xmy.cultivate.enums.ReadingStatusEnum;
import com.xmy.cultivate.enums.StatusGradeEnum;
import com.xmy.cultivate.excel.StudentGradeExcel;
import com.xmy.cultivate.exception.CommonException;
import com.xmy.cultivate.mapper.*;
import com.xmy.cultivate.respons.SchedulingGrade;
import com.xmy.cultivate.service.*;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.xmy.cultivate.util.CommonUtil;
import com.xmy.cultivate.util.DateUtil;
import com.xmy.cultivate.util.IdWorker;
import com.xmy.cultivate.util.ResultCode;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.text.ParseException;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.*;

/**
 * <p>
 * 班级 服务实现类
 * </p>
 *
 * @author min
 * @since 2022-07-26
 */
@Service
public class GradeServiceImpl extends ServiceImpl<GradeMapper, Grade> implements IGradeService {
    @Autowired
    IdWorker idWorker;

    @Resource
    @Lazy
    CourseMapper courseMapper;

    @Resource
    @Lazy
    GradeMapper gradeMapper;

    @Autowired
    @Lazy
    CompanyMapper companyMapper;

    @Autowired
    @Lazy
    OrderDetailMapper orderDetailMapper;

    @Autowired
    IStudentGradeService iStudentGradeService;

    @Autowired
    @Lazy
    StudentGradeMapper studentGradeMapper;

    @Autowired
    @Lazy
    ITypeValueDataService iTypeValueDataService;

    @Autowired
    @Lazy
    IRenewDataService iRenewDataService;

    @Autowired
    @Lazy
    ISubjectsService iSubjectsService;

    @Autowired
    @Lazy
    ICourseService iCourseService;

    @Autowired
    @Lazy
    ICourseSchedulingDetailService iCourseSchedulingDetailService;

    @Autowired
    @Lazy
    CourseSchedulingMapper courseSchedulingMapper;

    @Autowired
    @Lazy
    IQuarterService iQuarterService;

    @Autowired
    @Lazy
    IStaffService iStaffService;

    @Autowired
    @Lazy
    ITeacherContinueInfoService iTeacherContinueInfoService;

    @Autowired
    @Lazy
    IStudentService iStudentService;

    @Autowired
    @Lazy
    IDictService iDictService;

    @Autowired
    @Lazy
    IWecharsBindService iWecharsBindService;

    @Autowired
    @Lazy
    IStudentAccountService iStudentAccountService;

    @Autowired
    @Lazy
    ICourseTypeService iCourseTypeService;

    @Autowired
    @Lazy
    ICourseSchedulingAlwaysService iCourseSchedulingAlwaysService;

    @Autowired
    @Lazy
    ICourseSchedulingService iCourseSchedulingService;

    @Autowired
    @Lazy
    ILackCourseLogService iLackCourseLogService;

    @Autowired
    @Lazy
    IStudentLessonNumService iStudentLessonNumService;

    @Autowired
    @Lazy
    IMqPushService iMqPushService;

    @Autowired
    IStudentNewsService iStudentNewsService;

    @Autowired
    IStudentGradeContinueService iStudentGradeContinueService;


    @Transactional
    public Integer saveTo(Grade grade) throws ParseException {
        grade.setId(idWorker.nextId());
        List<TypeValueData> typeValueDataList = new ArrayList<>();

        Iterator<TypeValueData> iterator = grade.getTeacherList().iterator();
        Integer i = 0;
        Integer j = 0;
        while (iterator.hasNext()) {
            TypeValueData typeValueData = iterator.next();
            if (typeValueData.getValueId() != null && typeValueData.getTypeId() != null) {
                typeValueData.setForId(grade.getId());
                typeValueData.setType(21);
                typeValueDataList.add(typeValueData);
                /**
                 * 把第一位的老师和助教设置到班级上
                 */
                if (typeValueData.getTypeId() == 1) {
                    if (i == 0) {
                        grade.setTeacherId(typeValueData.getValueId());
                        i++;
                    }
                } else {
                    if (j == 0) {
                        grade.setHelpTeacherId(typeValueData.getValueId());
                        j++;
                    }
                }
            }
        }
        if (typeValueDataList.size() > 0) {
            iTypeValueDataService.saveBatch(typeValueDataList);
        }
        Course course = courseMapper.findOne(grade.getCourseId());
        grade.setYearClassId(course.getYearClassId());
        grade.setQuarterNum(course.getQuarterNum());

        Integer IsVacation = iDictService.getIsVacation(course.getQuarterNum());
        grade.setIsVacation(IsVacation);
        String schedulingType = "";
        //非补课班
        if (grade.getIsMakeup().equals(0) && grade.getIsAutoScheduling().equals(1)) {
            if (IsVacation.equals(0)) {
                Integer weekDates = Integer.parseInt(grade.getWeekDates());
                if (weekDates >= 1 && weekDates <= 5) {
                    schedulingType = "A类";
                } else {
                    schedulingType = "B类";
                }
            } else {
                if (grade.getWeekDates().equals("A")) {
                    schedulingType = "A天";
                } else {
                    schedulingType = "B天";
                }
            }
            grade.setIsScheduling(1);
        } else {
            grade.setIsScheduling(0);
            grade.setWeekDates("自由排");
        }
        Integer gradeSection = CommonUtil.getGradeSectionForYearClassId(course.getYearClassId().getKey());
        LocalDate openDate = iCourseSchedulingAlwaysService.getStartDate(grade.getYearPart(), course.getQuarterNum(), gradeSection, null);
        LocalDate endDate = iCourseSchedulingAlwaysService.getEndDate(grade.getYearPart(), course.getQuarterNum(), gradeSection, null);
        if (openDate == null) {
            //throw new CommonException(ResultCode.OPEN_DATE_NULL);
        }
        if (endDate == null) {
//            throw new CommonException(ResultCode.END_DATE_NULL);
        }

        if (openDate != null) {
            grade.setOpenDate(openDate);
        }
        if (endDate != null) {
            grade.setEndDate(endDate);
        }
        grade.setSchedulingType(schedulingType);
        this.save(grade);
        //非补课班自动排课
        Integer schedulintCount = 0;
        if (grade.getIsMakeup().equals(0)) {
            //schedulintCount = iCourseSchedulingService.autoScheduling(grade.getId(), null);
            //iMqPushService.autoScheduling(grade.getId(),null);//做了事物处理，异步不能放在这里
        }

        Staff staff = iStaffService.getById(grade.getTeacherId());
        UpdateWrapper<CourseSchedulingDetail> courseSchedulingDetailUpdateWrapper = new UpdateWrapper<>();
        courseSchedulingDetailUpdateWrapper.eq("grade_id", grade.getId());
        courseSchedulingDetailUpdateWrapper.ge("school_date", LocalDate.now());
        courseSchedulingDetailUpdateWrapper.set("grade_name", grade.getName());
        courseSchedulingDetailUpdateWrapper.set("teacher_id", grade.getTeacherId());
        courseSchedulingDetailUpdateWrapper.set("teacher_name", staff.getName());
        courseSchedulingDetailUpdateWrapper.set("subjects_id", course.getSubjectsId());
        courseSchedulingDetailUpdateWrapper.set("subjects_name", CommonUtil.getSubjectsNameForId(Integer.parseInt(course.getSubjectsId().toString())));
        iCourseSchedulingDetailService.update(courseSchedulingDetailUpdateWrapper);

        //更新课次
        //iCourseSchedulingDetailService.updateLessonNum(grade.getId());
        return schedulintCount;
    }

    @Transactional
    public Integer updateTo(Grade grade) throws ParseException {
        Grade gradeOld = this.getById(grade.getId());
        List<TypeValueData> typeValueDataList = new ArrayList<>();
        List<TypeValueData> upTypeValueDataList = new ArrayList<>();
        Set<Long> atTypeValueData = new HashSet<>();

        Integer i = 0;
        Integer j = 0;
        Iterator<TypeValueData> iterator = grade.getTeacherList().iterator();
        while (iterator.hasNext()) {
            TypeValueData typeValueData = iterator.next();

            if (typeValueData.getValueId() != null && typeValueData.getTypeId() != null) {
                if (typeValueData.getId() == null) {
                    typeValueData.setForId(grade.getId());
                    typeValueData.setType(21);
                    typeValueDataList.add(typeValueData);
                } else {
                    typeValueData.setForId(grade.getId());
                    typeValueData.setType(21);
                    upTypeValueDataList.add(typeValueData);
                    atTypeValueData.add(typeValueData.getId());
                }

                /**
                 * 把第一位的老师和助教设置到班级上
                 */
                if (typeValueData.getTypeId() == 1) {
                    if (i == 0) {
                        grade.setTeacherId(typeValueData.getValueId());
                        i++;
                    }
                } else {
                    if (j == 0) {
                        grade.setHelpTeacherId(typeValueData.getValueId());
                        j++;
                    }
                }
            }
        }

        //删除
        if (atTypeValueData.size() > 0) {
            //System.out.print("grade:"+grade.getId());
            //System.out.print(atTypeValueData);
            QueryWrapper<TypeValueData> queryWrapper = new QueryWrapper<>();
            queryWrapper.notIn("id", atTypeValueData);
            queryWrapper.eq("for_id", grade.getId());
            iTypeValueDataService.remove(queryWrapper);
        } else {
            QueryWrapper<TypeValueData> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("for_id", grade.getId());
            iTypeValueDataService.remove(queryWrapper);
        }
        //新增
        if (typeValueDataList.size() > 0) {
            iTypeValueDataService.saveBatch(typeValueDataList);
        }
        //修改
        if (upTypeValueDataList.size() > 0) {
            iTypeValueDataService.updateBatchById(upTypeValueDataList, upTypeValueDataList.size());
        }

        Course course = iCourseService.getById(grade.getCourseId());
        grade.setSubjectsId(course.getSubjectsId());
        grade.setYearClassId(course.getYearClassId());
        grade.setQuarterNum(course.getQuarterNum());
        grade.setIsScheduling(1);
        Integer IsVacation = iDictService.getIsVacation(course.getQuarterNum());
        grade.setIsVacation(IsVacation);
        String schedulingType = "";
        if (grade.getIsMakeup().equals(0) && grade.getIsAutoScheduling().equals(1)) {
            if (IsVacation.equals(0)) {
                Integer weekDates = Integer.parseInt(grade.getWeekDates());
                if (weekDates >= 1 && weekDates <= 5) {
                    schedulingType = "A类";
                } else {
                    schedulingType = "B类";
                }
            } else {
                if (grade.getWeekDates().equals("A")) {
                    schedulingType = "A天";
                } else {
                    schedulingType = "B天";
                }
            }
        } else {
            grade.setIsScheduling(0);
            grade.setWeekDates("自由排");
        }
        Integer gradeSection = CommonUtil.getGradeSectionForYearClassId(course.getYearClassId().getKey());
        LocalDate openDate = iCourseSchedulingAlwaysService.getStartDate(grade.getYearPart(), course.getQuarterNum(), gradeSection, null);
        LocalDate endDate = iCourseSchedulingAlwaysService.getEndDate(grade.getYearPart(), course.getQuarterNum(), gradeSection, null);
        if (openDate == null) {
            //throw new CommonException(ResultCode.OPEN_DATE_NULL);
        }
        if (endDate == null) {
//            throw new CommonException(ResultCode.END_DATE_NULL);
        }

        if (openDate != null) {
            grade.setOpenDate(openDate);
        }
        if (endDate != null) {
            grade.setEndDate(endDate);
        }
        
        grade.setSchedulingType(schedulingType);
        //修改主体
        this.updateById(grade);


        //更新排课信息里的课程科目，以后调整到异步修改
        UpdateWrapper<CourseSchedulingDetail> courseSchedulingDetailUpdateWrapper = new UpdateWrapper<>();
        Subjects subjects = iSubjectsService.getById(course.getSubjectsId());
        courseSchedulingDetailUpdateWrapper.eq("grade_id", grade.getId());
        courseSchedulingDetailUpdateWrapper.set("grade_name", grade.getName());
        courseSchedulingDetailUpdateWrapper.set("course_id", course.getId());
        courseSchedulingDetailUpdateWrapper.set("course_name", course.getName());
        courseSchedulingDetailUpdateWrapper.set("subjects_id", course.getSubjectsId());
        courseSchedulingDetailUpdateWrapper.set("subjects_name", subjects.getName());
        courseSchedulingDetailUpdateWrapper.set("teacher_id", grade.getTeacherId());
        Staff staff = iStaffService.getById(grade.getTeacherId());
        if (!Objects.isNull(staff)) {
            courseSchedulingDetailUpdateWrapper.set("teacher_name", staff.getName());
        }

        iCourseSchedulingDetailService.update(null, courseSchedulingDetailUpdateWrapper);

        if (grade.getLessonType().equals(1)) {
            if (!grade.getTeacherId().equals(gradeOld.getTeacherId())) {
                courseSchedulingDetailUpdateWrapper.clear();
                courseSchedulingDetailUpdateWrapper.eq("grade_id", grade.getId());
                courseSchedulingDetailUpdateWrapper.eq("grade_name", grade.getName());
                courseSchedulingDetailUpdateWrapper.ge("school_date", LocalDate.now());
                courseSchedulingDetailUpdateWrapper.set("teacher_id", grade.getTeacherId());
                Staff staffInfo = iStaffService.getById(grade.getTeacherId());
                if (staffInfo != null) {
                    courseSchedulingDetailUpdateWrapper.set("teacher_name", staffInfo.getName());
                }
                iCourseSchedulingDetailService.update(null, courseSchedulingDetailUpdateWrapper);
            }
        }

        if (gradeOld.getCourseTypeId() != grade.getCourseTypeId()) {
            iStudentAccountService.updateClassTypeForGrade(grade);
        }

        //类型修改后，要把已存在的排课信息删除
        if (grade.getIsMakeup() != gradeOld.getIsMakeup()) {
            QueryWrapper<CourseSchedulingDetail> courseSchedulingDetailQueryWrapper = new QueryWrapper<>();
            courseSchedulingDetailQueryWrapper.eq("grade_id", grade.getId());
            courseSchedulingDetailQueryWrapper.eq("status", 0);
            iCourseSchedulingDetailService.remove(courseSchedulingDetailQueryWrapper);
        }

        //原来为自动排课，调整为不排课
        if (gradeOld.getIsAutoScheduling().equals(1) && grade.getIsAutoScheduling().equals(0)) {
            QueryWrapper<CourseSchedulingDetail> courseSchedulingDetailQueryWrapper = new QueryWrapper<>();
            courseSchedulingDetailQueryWrapper.eq("grade_id", grade.getId());
            courseSchedulingDetailQueryWrapper.eq("status", 0);
            iCourseSchedulingDetailService.remove(courseSchedulingDetailQueryWrapper);
        }

        //非补课班自动排课
        Integer schedulintCount = 0;
        if (grade.getIsMakeup().equals(0) && grade.getIsAutoScheduling().equals(1)) {
            if (!gradeOld.getWeekDates().equals(grade.getWeekDates())) {
                schedulintCount = iCourseSchedulingService.autoScheduling(grade.getId(), LocalDate.now());
                //iMqPushService.autoScheduling(grade.getId(),LocalDate.now());
            } else {
                if (!gradeOld.getTimeStart().equals(grade.getTimeStart()) || !gradeOld.getTimeEnd().equals(grade.getTimeEnd())) {
                    QueryWrapper<CourseSchedulingDetail> courseSchedulingDetailQueryWrapper = new QueryWrapper<>();
                    courseSchedulingDetailQueryWrapper.eq("grade_id", grade.getId());
                    courseSchedulingDetailQueryWrapper.ge("start_date_time", LocalDateTime.now().withNano(0));
                    List<CourseSchedulingDetail> courseSchedulingDetailList = iCourseSchedulingDetailService.list(courseSchedulingDetailQueryWrapper);
                    for (CourseSchedulingDetail courseSchedulingDetail : courseSchedulingDetailList) {
                        LocalDateTime startDateTime = DateUtil.StrToDateTime(courseSchedulingDetail.getSchoolDate() + "T" + grade.getTimeStart() + ":00");
                        LocalDateTime endDateTime = DateUtil.StrToDateTime(courseSchedulingDetail.getSchoolDate() + "T" + grade.getTimeEnd() + ":00");
                        courseSchedulingDetail.setStartDateTime(startDateTime);
                        courseSchedulingDetail.setEndDateTime(endDateTime);
                        courseSchedulingDetail.setTimeStart(grade.getTimeStart());
                        courseSchedulingDetail.setTimeEnd(grade.getTimeEnd());
                        iCourseSchedulingDetailService.updateById(courseSchedulingDetail);
                    }
                }
            }
        }


        //更新课次
        //iCourseSchedulingDetailService.updateLessonNum(grade.getId());
        return schedulintCount;
    }

    public IPage<Grade> checkGrade(IPage<?> page, Wrapper wrapper, Long schoolId) {
        IPage<Grade> iPage = gradeMapper.checkGrade(page, wrapper);
        List<Grade> gradeList = iPage.getRecords();
        for (Grade grade : gradeList) {
            Course course = grade.getCourseObj();
            List<CoursePricing> coursePricingList = courseMapper.coursePricingForSchoolIdList(course.getId(), schoolId);
            course.setCoursePricingList(coursePricingList);

            QueryWrapper<Grade> gradeQueryWrapper = new QueryWrapper<>();
            gradeQueryWrapper.eq("deleted", 0);
            gradeQueryWrapper.eq("school_id", schoolId);
            gradeQueryWrapper.eq("course_id", course.getId());
            List<Grade> gradeList1 = gradeMapper.selectList(gradeQueryWrapper);
            course.setGradeList(gradeList1);
        }
        return iPage;
    }
    /*public List<Map<String,Object>> checkGrade(Map<String,Object> map){
        List<Map<String,Object>> mapList = gradeMapper.checkGrade(map);
        Iterator iterator = mapList.iterator();
        while (iterator.hasNext()){
            Map<String,Object> map1 = (Map<String, Object>) iterator.next();
            List<Map<String,Object>> mapList2 = courseMapper.coursePricingForSchoolIdList(Long.valueOf(String.valueOf(map1.get("course_id"))),Long.valueOf(String.valueOf(map.get("school_id"))));
            map1.put("coursePricingList",mapList2);
        }
          return mapList;
    }*/


    public IPage<Grade> findAll(IPage<?> page, Wrapper wrapper) {
        IPage<Grade> gradeIPage = gradeMapper.findAll(page, wrapper);
        for (Grade grade : gradeIPage.getRecords()) {
            Integer count = studentGradeMapper.studentCount(grade.getSchoolObj().getId(), grade.getId());
            Integer advanceCount = studentGradeMapper.studentAdvanceCount(grade.getSchoolObj().getId(), grade.getId());
            grade.setCount(count);
            grade.setAdvanceCount(advanceCount);
                /*QueryWrapper<ArrangingExcel> courseSchedulingQueryWrapper = new QueryWrapper<>();
                courseSchedulingQueryWrapper.eq("grade_id",grade.getId());
                Long schedulingCount = courseSchedulingMapper.selectCount(courseSchedulingQueryWrapper);
                if(schedulingCount>0){
                    grade.setIsScheduling(1);
                }else {
                    grade.setIsScheduling(0);
                }*/
        }

        return gradeIPage;
    }

    public List<Long> findGradeIdList(Wrapper wrapper) {
        return gradeMapper.findGradeIdList(wrapper);
    }

    public Grade getOneForId(Long id) {
        Grade grade = gradeMapper.getOneForId(id);
        Integer count = studentGradeMapper.studentCount(grade.getSchoolObj().getId(), grade.getId());
        grade.setStudentCount(count);
        CourseType courseType = iCourseTypeService.getById(grade.getCourseTypeId());
        if (courseType != null) {
            grade.setCourseTypeName(courseType.getName());
        }

        return grade;
    }

    @Override
    public List<Grade> getGradeForCheck(Long schoolId, Long courseId, Integer yearPart, Integer quarterNum, List<Long> gradeIdList, Long studentId) {
        Course course = iCourseService.getById(courseId);
        StudentGrade studentGrade = null;
        if (studentId != null) {
            QueryWrapper<StudentGrade> studentGradeQueryWrapper = new QueryWrapper<>();
            studentGradeQueryWrapper.eq("year_part", yearPart);
            studentGradeQueryWrapper.eq("quarter_num", quarterNum);
            studentGradeQueryWrapper.eq("school_id", schoolId);
            studentGradeQueryWrapper.eq("subjects_id", course.getSubjectsId());
            studentGradeQueryWrapper.eq("student_id", studentId);
            studentGradeQueryWrapper.eq("lesson_type", 1);
            studentGradeQueryWrapper.in("reading_status", 1);
            studentGradeQueryWrapper.last("limit 1");
            studentGrade = iStudentGradeService.getOne(studentGradeQueryWrapper);
        }

        //获取班级开了该课程的班级
        QueryWrapper<Grade> gradeQueryWrapper = new QueryWrapper<>();
        gradeQueryWrapper.eq("deleted", 0);
        gradeQueryWrapper.eq("school_id", schoolId);
        gradeQueryWrapper.eq("course_id", courseId);
        gradeQueryWrapper.eq("year_part", yearPart);
        gradeQueryWrapper.eq("quarter_num", quarterNum);
        gradeQueryWrapper.eq("status", 1);

        if (studentGrade != null) {
            gradeQueryWrapper.eq("id", studentGrade.getGradeId());
        }

        if (gradeIdList.size() > 0) {
            gradeQueryWrapper.in("id", gradeIdList);
        }
        List<Grade> gradeList = gradeMapper.selectList(gradeQueryWrapper);
        for (Grade grade : gradeList) {
            Staff staff = iStaffService.getById(grade.getTeacherId());
            grade.setTeacherName(staff.getName());
            Long count = this.getGradeStudentCount(grade.getId());
            grade.setStudentCount(Integer.parseInt(count.toString()));
            String courseTypeName = iCourseTypeService.getNameForId(grade.getCourseTypeId());
            grade.setCourseTypeName(courseTypeName);
        }

        return gradeList;
    }

    public Long getGradeStudentCount(Long gradeId) {
        QueryWrapper<StudentGrade> studentGradeQueryWrapper = new QueryWrapper<>();
        studentGradeQueryWrapper.eq("grade_id", gradeId);
        studentGradeQueryWrapper.eq("deleted", 0);
        studentGradeQueryWrapper.ne("status", 3);
        studentGradeQueryWrapper.and(i -> i.eq("reading_status", 1).or().gt("use_course_count", 0));
        Long count = studentGradeMapper.selectCount(studentGradeQueryWrapper);
        return count;
    }


    @Transactional
    public Boolean addStudent(String gradeId, String[] studentIdList) {

        Grade grade = gradeMapper.selectById(Long.parseLong(gradeId));
        Course course = courseMapper.selectById(grade.getCourseId());
        Integer yearPartAndQuarter = Integer.parseInt(grade.getYearPart() + "" + course.getQuarterNum());
        List<StudentGrade> studentGradeList = new ArrayList<>();

        for (String studentId : studentIdList) {
            //剩余课时
            Integer courseHouse = orderDetailMapper.getResidueCourseCountForSubjects(grade.getSchoolId(), Long.parseLong(studentId), course.getSubjectsId(), yearPartAndQuarter, grade.getLessonType());
            OrderDetail orderDetail = orderDetailMapper.getLastOneForSubjectId(grade.getSchoolId(), Long.parseLong(studentId), course.getSubjectsId(), grade.getYearPart(), course.getQuarterNum(), grade.getLessonType());
            if (orderDetail == null) {
                continue;
            }

            Integer isAtGrade = studentGradeMapper.studentIsAtGrade(Long.parseLong(studentId), grade.getId());
            //System.out.print("isAtGrade:"+isAtGrade);
            if (isAtGrade == 0) {
                StudentGrade studentGrade = new StudentGrade();
                studentGrade.setSchoolId(grade.getSchoolId());
                studentGrade.setGradeId(grade.getId());
                studentGrade.setCourseId(grade.getCourseId());
                studentGrade.setSubjectsId(course.getSubjectsId());
                studentGrade.setYearPart(grade.getYearPart());
                studentGrade.setQuarterNum(course.getQuarterNum());
                studentGrade.setSurplusCourseNum(courseHouse);
                studentGrade.setStudentId(Long.parseLong(studentId));
                studentGrade.setLessonType(grade.getLessonType());
                studentGrade.setYearClassId(course.getYearClassId().getKey());//年级
                studentGrade.setClassTypeIdNew(grade.getCourseTypeId());
                if (orderDetail != null) {
                    studentGrade.setOrderDetailId(orderDetail.getId());
                }
                //System.out.print("添加成功:"+isAtGrade);
                studentGradeMapper.insert(studentGrade);
                iRenewDataService.updateTeacher(grade.getSchoolId(), Long.parseLong(studentId), course, grade);
                if (course.getLessonType().equals(1)) {
                    //if (course.getSubjectsId().equals(1L)) {
                    //    iStudentAccountService.applyAddStudentAccount(grade.getSchoolId(), orderDetail.getStudentId(), grade.getId(), course.getId());
                    //}
                    //同步帐号信息到其它系统
                    //iMqPushService.updateStudentAccount(orderDetail.getStudentId(),orderDetail.getSubjectsId());
                    iLackCourseLogService.batchAdd(grade.getYearPart(), course.getQuarterNum(), grade.getSchoolId(), orderDetail.getStudentId(), course.getSubjectsId(), course.getYearClassId().getKey(), grade.getId(), 1, 1);
                }
            }
            //更新为最后一条
            iStudentGradeService.updateIsLast(grade.getYearPart(), course.getQuarterNum(), orderDetail.getStudentId(), orderDetail.getSubjectsId(), grade.getLessonType());

            //添加学生课次
            //iStudentLessonNumService.addStudentLesson(grade.getId(), Long.parseLong(studentId));
            iMqPushService.addStudentLesson(grade.getId(), Long.parseLong(studentId));


        }
        return true;
    }

    /**
     * 添加预分班
     *
     * @param gradeId
     * @param studentIdList
     * @return
     */
    @Transactional
    public Boolean presortGrade(String gradeId, String[] studentIdList) {

        Quarter quarter = iQuarterService.getNowQuarter();

        Grade grade = gradeMapper.selectById(Long.parseLong(gradeId));
        Course course = courseMapper.selectById(grade.getCourseId());
        Integer yearPartAndQuarter = Integer.parseInt(quarter.getYearPart() + "" + quarter.getNum());
        LocalDateTime localDateTime = LocalDateTime.now().withNano(0);

        List<StudentGrade> studentGradeList = new ArrayList<>();
        for (String studentId : studentIdList) {
            //剩余课时
            Integer courseHouse = orderDetailMapper.getResidueCourseCountForSubjects(null, Long.parseLong(studentId), course.getSubjectsId(), yearPartAndQuarter, grade.getLessonType());
            OrderDetail orderDetail = orderDetailMapper.getLastOneForSubjectId(grade.getSchoolId(), Long.parseLong(studentId), course.getSubjectsId(), grade.getYearPart(), course.getQuarterNum(), grade.getLessonType());

            Integer isAtGrade = studentGradeMapper.studentIsAtGrade(Long.parseLong(studentId), grade.getId());
            //System.out.print("isAtGrade:"+isAtGrade);

            Integer isPresort = 0;

            if (courseHouse < 3) {
                isPresort = 4;
            } else {
                Integer perCount = studentGradeMapper.getPresortCount(grade.getYearPart(), grade.getQuarterNum(), course.getSubjectsId(), Long.parseLong(studentId), grade.getLessonType(), "1,2,3");
                if (perCount == 0) {
                    isPresort = 1;
                }
            }

            if (isAtGrade > 0) {
                continue;
            }
            StudentGrade studentGrade = new StudentGrade();
            studentGrade.setId(idWorker.nextId());
            studentGrade.setLessonType(grade.getLessonType());
            studentGrade.setSchoolId(grade.getSchoolId());
            studentGrade.setGradeId(grade.getId());
            studentGrade.setCourseId(grade.getCourseId());
            studentGrade.setYearClassId(grade.getYearClassId().getKey());
            studentGrade.setSubjectsId(course.getSubjectsId());
            studentGrade.setYearPart(grade.getYearPart());
            studentGrade.setQuarterNum(course.getQuarterNum());
            studentGrade.setSurplusCourseNum(courseHouse);
            studentGrade.setStudentId(Long.parseLong(studentId));
            studentGrade.setIsPresort(isPresort);
            studentGrade.setReadingStatus(ReadingStatusEnum.NO);
            studentGrade.setClassTypeIdNew(grade.getCourseTypeId());
            if (orderDetail != null) {
                studentGrade.setOrderDetailId(orderDetail.getId());
            }
            studentGradeMapper.insert(studentGrade);
            iStudentGradeContinueService.addData(studentGrade,1);//添加到预分班
            //iRenewDataService.updateTeacher(grade.getSchoolId(), Long.parseLong(studentId), course, grade);
            iMqPushService.updateReNewTeacher(grade.getId(), Long.parseLong(studentId), course.getId(), grade.getId());
            //更新为最后一条
            //iStudentGradeService.updateIsLast(grade.getYearPart(), course.getQuarterNum(), Long.parseLong(studentId), course.getSubjectsId(), grade.getLessonType());
            iMqPushService.updateStudentGradeLast(grade.getYearPart(), course.getQuarterNum(), Long.parseLong(studentId), course.getSubjectsId(), grade.getLessonType());
            //添加学生课次
            //iStudentLessonNumService.addStudentLesson(grade.getId(), Long.parseLong(studentId));
            iMqPushService.addStudentLesson(grade.getId(), Long.parseLong(studentId));

            //智能课、刷题班分班
            iMqPushService.autoAllotStudentGrade(studentGrade);

            /**
             * 获取上一个学期
             */
            Quarter lastQuarter = iQuarterService.getLastQuarter(studentGrade.getYearPart(), studentGrade.getQuarterNum());

            Quarter presortQuarter = iQuarterService.getQuarterForYearAndNum(grade.getYearPart(), grade.getQuarterNum());
            iMqPushService.updateStudentAccount(grade.getYearPart(), grade.getQuarterNum(), Long.parseLong(studentId), course.getSubjectsId());

            //获取上一学期最后一次分班信息
            StudentGrade studentGradeLast = iStudentGradeService.getLastStudentGradeForOrderDetailId(studentGrade.getSchoolId(), studentGrade.getStudentId(), studentGrade.getSubjectsId(), lastQuarter.getYearPart(), lastQuarter.getNum(), grade.getLessonType());
            if (studentGradeLast != null) {
                Grade gradeContinueInfo = gradeMapper.selectById(studentGradeLast.getGradeId());
                QueryWrapper<TeacherContinueInfo> teacherContinueInfoQueryWrapper = new QueryWrapper<>();
                teacherContinueInfoQueryWrapper.eq("school_id", studentGrade.getSchoolId());
                teacherContinueInfoQueryWrapper.eq("subjects_id", studentGrade.getSubjectsId());
                teacherContinueInfoQueryWrapper.eq("teacher_id", gradeContinueInfo.getTeacherId());
                teacherContinueInfoQueryWrapper.eq("year_part", studentGradeLast.getYearPart());
                teacherContinueInfoQueryWrapper.eq("quarter_num", studentGradeLast.getQuarterNum());
                teacherContinueInfoQueryWrapper.eq("student_id", Long.parseLong(studentId));
                teacherContinueInfoQueryWrapper.eq("status", 1);

                Long tcCount = iTeacherContinueInfoService.count(teacherContinueInfoQueryWrapper);
                if (tcCount.equals(0L)) {
                    TeacherContinueInfo teacherContinueInfo = new TeacherContinueInfo();
                    teacherContinueInfo.setId(studentGrade.getId());
                    BeanUtils.copyProperties(studentGrade, teacherContinueInfo);
                    teacherContinueInfo.setYearPart(lastQuarter.getYearPart());
                    teacherContinueInfo.setYearClassId(grade.getYearClassId().getKey());
                    teacherContinueInfo.setQuarterNum(lastQuarter.getNum());
                    teacherContinueInfo.setGradeId(studentGradeLast.getGradeId());
                    teacherContinueInfo.setAddDate(LocalDate.now());
                    teacherContinueInfo.setStudentGradeId(studentGrade.getId());
                    teacherContinueInfo.setTeacherId(gradeContinueInfo.getTeacherId());
                    iTeacherContinueInfoService.save(teacherContinueInfo);
                }
            }

            try {
                Student student = iStudentService.getById(studentId);
                Subjects subjects = iSubjectsService.getById(course.getSubjectsId());
                Dict dict = iDictService.getQuarter(studentGrade.getQuarterNum());

                List<String> opendIdList = iWecharsBindService.getSendOpenid(student.getId());
                StringBuilder first = new StringBuilder();
                first.append("");
                StringBuilder keyword1 = new StringBuilder();
                StringBuilder keyword2 = new StringBuilder();
                keyword1.append(student.getName());
                Staff staff = iStaffService.getById(grade.getTeacherId());
                String gradeReplace = CommonUtil.replaceGradeName(grade.getName(), staff.getName(), student.getName(), subjects.getName());
                keyword2.append("恭喜报名" + presortQuarter.getAliasName() + ":").append(gradeReplace).append("成功");
                StringBuilder remark = new StringBuilder();
                remark.append("");
                iWecharsBindService.presortGrade(opendIdList, first.toString(), keyword1.toString(), keyword2.toString(), remark.toString(), localDateTime + "" + student.getId());
            } catch (Exception e) {
                System.out.println("teacherContinueInfo:" + e.getMessage());
            }
        }
        return true;
    }

    public Boolean endOfShift(Long gradeId) {
        Grade grade = gradeMapper.selectById(gradeId);
        boolean rs = false;
        if (grade != null) {
            LocalDate dateNow = LocalDate.now();
            if (grade.getStatus().equals(StatusGradeEnum.NORMAL)) {
                grade.setStatus(StatusGradeEnum.DISABLE);
                grade.setFinishDate(dateNow);
                gradeMapper.updateById(grade);

                //设置班里的学生为结课
                QueryWrapper<StudentGrade> studentGradeQueryWrapper = new QueryWrapper<>();
                studentGradeQueryWrapper.eq("grade_id", gradeId);
                studentGradeQueryWrapper.eq("deleted", 0);
                studentGradeQueryWrapper.eq("status", 1);
                studentGradeQueryWrapper.eq("reading_status", 1);
                List<StudentGrade> studentGradeList = studentGradeMapper.selectList(studentGradeQueryWrapper);

                for (StudentGrade studentGrade : studentGradeList) {
                    studentGrade.setReadingStatus(ReadingStatusEnum.FINISH);
                    studentGradeMapper.updateById(studentGrade);
                }

                    /*
                    List<Integer> readingStatusList = new ArrayList<>();
                    readingStatusList.add(1);
                    readingStatusList.add(4);
                    UpdateWrapper<StudentGrade> studentGradeUpdateWrapper = new UpdateWrapper<>();
                    studentGradeUpdateWrapper.eq("grade_id",gradeId);
                    studentGradeUpdateWrapper.eq("status",1);
                    studentGradeUpdateWrapper.eq("deleted",0);
                    studentGradeUpdateWrapper.in("reading_status",readingStatusList);
                    studentGradeUpdateWrapper.set("reading_status",5);
                    studentGradeMapper.update(null,studentGradeUpdateWrapper);*/
                rs = true;
            }
        }
        return rs;
    }

    /**
     * @return
     */
    public List<Grade> getRepairGrade(String schoolId, String courseId, String subjectsId, String gradeName, String lessonType, Integer yearPart, Integer quarterNum) {
        QueryWrapper<Grade> gradeQueryWrapper = new QueryWrapper<>();
        //gradeQueryWrapper.eq("deleted",0);
        gradeQueryWrapper.eq(StringUtils.isNotBlank(schoolId), "school_id", schoolId);
        gradeQueryWrapper.like(StringUtils.isNotBlank(gradeName), "name", gradeName);
        gradeQueryWrapper.like(StringUtils.isNotBlank(lessonType), "lesson_type", lessonType);
        gradeQueryWrapper.eq("year_part", yearPart);
        if (StringUtils.isNotBlank(subjectsId)) {
            gradeQueryWrapper.inSql("course_id", "select id from course where subjects_id = " + subjectsId + " and quarter_num = " + quarterNum + " ");
        }
        //gradeQueryWrapper.inSql("course_id", "select id from course where id = " + courseId + " and quarter_num = " + quarterNum + " ");
        //gradeQueryWrapper
        List<Grade> gradeList = gradeMapper.selectList(gradeQueryWrapper);
        return gradeList;
    }

    @Override
    public List<SchedulingGrade> getGradeListForScheduling(Long schoolId, Integer subjectsId, Integer yearPart, Integer qurarterNum, String weekDates, Integer lessonType, Integer sourseLeve, Long adminId) {
        return gradeMapper.getGradeListForScheduling(schoolId, subjectsId, yearPart, qurarterNum, weekDates, lessonType, sourseLeve, adminId);
    }

    @Override
    public List<String> getSchoolTimeList(Long schoolId, Integer yearPart, Integer qurarterNum, String weekDates, Integer lessonType) {
        return gradeMapper.getSchoolTimeList(schoolId, yearPart, qurarterNum, weekDates, lessonType);
    }

    @Override
    public String getGradeTime(Long schoolId, Integer subjectsId, Integer yearPart, Integer qurarterNum, String weekDates, Integer lessonType) {
        return gradeMapper.getGradeTime(schoolId, subjectsId, yearPart, qurarterNum, weekDates, lessonType);
    }

    @Override
    public boolean agrainGrade(Grade grade) {
        grade.setStatus(StatusGradeEnum.NORMAL);
        studentGradeMapper.agrainForGrade(grade.getYearPart(), grade.getQuarterNum(), grade.getId());
        this.updateById(grade);
        return true;
    }

    @Override
    public Grade getGradeOneForTeacherId(Integer yearPart, Integer qurarterNum, Long teacherId, Integer lessonType) {
        return gradeMapper.getGradeOneForTeacherId(yearPart, qurarterNum, teacherId, lessonType);
    }

    @Override
    public List<StudentGradeExcel> workingScheduleNew(String schoolIdList, String name, String yearClassIdList, String subjectsId, String status, String classRoomIdList, String courseIdList, String yearPart, String quarterNumList, String teacherId, String isCheckHouse, String lessonType, String gradeIdList) {
        Quarter quarter = iQuarterService.getNowQuarter();
        Integer oldYearPart = quarter.getYearPart();
        Integer oldQuarterNum = quarter.getNum();

        if (StringUtils.isBlank(yearPart)) {
            yearPart = String.valueOf(oldYearPart);
        }
        if (StringUtils.isBlank(quarterNumList)) {
            quarterNumList = String.valueOf(oldQuarterNum);
        }

        return gradeMapper.workingScheduleNew(schoolIdList, name, yearClassIdList, subjectsId, status, classRoomIdList, courseIdList, yearPart, quarterNumList, teacherId, lessonType, gradeIdList, oldYearPart, oldQuarterNum);
    }

    @Override
    public List<StudentGradeExcel> workingScheduleBeforehandNew(String schoolIdList, String name, String yearClassIdList, String subjectsId, String status, String classRoomIdList, String courseIdList, String yearPart, String quarterNumList, String teacherId, String isCheckHouse, String lessonType, String gradeIdList) {
        // 获取当前学期（因为是预分班，所以需要获取当前学期用来查询通关数、正确率和分数）
        Quarter quarter = iQuarterService.getNowQuarter();
        Integer oldYearPart = quarter.getYearPart();
        Integer oldQuarterNum = quarter.getNum();

        return gradeMapper.workingScheduleBeforehandNew(schoolIdList, name, yearClassIdList, subjectsId, status, classRoomIdList, courseIdList, yearPart, quarterNumList, teacherId, lessonType, gradeIdList, oldYearPart, oldQuarterNum);
    }

    @Override
    public List<StudentGradeExcel> workingSchedulAccount(String schoolIdList, String name, String yearClassIdList, String subjectsId, String status, String classRoomIdList, String courseIdList, String yearPart, String quarterNumList, String teacherId, String isCheckHouse, String lessonType, String gradeIdList) {
        Quarter quarter = iQuarterService.getNowQuarter();
        Integer oldYearPart = quarter.getYearPart();
        Integer oldQuarterNum = quarter.getNum();

        if (StringUtils.isBlank(yearPart)) {
            yearPart = String.valueOf(oldYearPart);
        }
        if (StringUtils.isBlank(quarterNumList)) {
            quarterNumList = String.valueOf(oldQuarterNum);
        }

        return gradeMapper.workingScheduleAccount(schoolIdList, name, yearClassIdList, subjectsId, status, classRoomIdList, courseIdList, yearPart, quarterNumList, teacherId, lessonType, gradeIdList, oldYearPart, oldQuarterNum);
    }

    @Override
    public IPage<Grade> getGradePosition(IPage<?> page, Wrapper wrapper) {
        return gradeMapper.getGradePosition(page, wrapper);
    }

    public List<Grade> getPositionGradeList(Integer yearPart, Integer quarterNum, Long schoolId, Long subjectsId, Integer yearClassId, Integer lessonType, Integer type, BigDecimal score, Long classTypeId) {
        return gradeMapper.getPositionGradeList(yearPart, quarterNum, schoolId, subjectsId, yearClassId, lessonType, type, score, classTypeId);
    }

    @Override
    public IPage<Grade> getGradeFloatList(IPage<?> page, String yearPart, String quarterNum, String yearClassId, String courseTypeId, String subjectsId, String schoolId, String teacherId, String classRoomId, String gradeId, String isDescOrAsc, String isFieldToSc, String iSeal, String startDate, String endDate) {
        return gradeMapper.getGradeFloatList(page, yearPart, quarterNum, yearClassId, courseTypeId, subjectsId, schoolId, teacherId, classRoomId, gradeId, isDescOrAsc, isFieldToSc, iSeal, startDate, endDate);
    }

    /**
     * 班级列表中的课程表（单科）
     *
     * @param page
     * @param gradeId
     * @return
     */
    @Override
    public IPage<Grade> timetableByGradeId(IPage<?> page, Integer yearPart, Integer quarterNum, String gradeId, String subjectsId, Integer status, String studentName, Integer lessonType) {

        return gradeMapper.timetableByGradeId(page, yearPart, quarterNum, gradeId, subjectsId, status, studentName, lessonType);
    }

    /**
     * 班级列表中的课程表（多科）
     *
     * @param page
     * @param gradeId
     * @return
     */
    @Override
    public IPage<Grade> timetableByGradeIdList(IPage<?> page, Integer yearPart, Integer quarterNum, String gradeId, String subjectsId, String schoolId, String classRoomIdList, String courseIdList, String yearClassIdList, String name, String teacherId) {
        return gradeMapper.timetableByGradeIdList(page, yearPart, quarterNum, gradeId, subjectsId, schoolId, classRoomIdList, courseIdList, yearClassIdList, name, teacherId);
    }
}
